package code.structure.module.scene.manager
{
	import code.structure.manager.mouse.MouseManager;
	import code.structure.manager.sound.MySoundManager;
	import code.structure.module.configs.data.ItemConfigData;
	import code.structure.module.scene.SceneController;
	import code.structure.module.scene.model.SceneModel;
	import code.structure.module.scene.model.data.SceneItemData;
	import code.structure.module.scene.view.YIsoWorld;
	import code.structure.module.scene.view.iso.FloorIsoObject;
	import code.structure.module.scene.view.iso.WallIsoObject;
	import code.structure.module.scene.view.iso.WallMuralIsoObject;
	import code.structure.module.scene.view.iso.YIsoObject;
	import code.structure.module.scene.view.iso.product.ProductTreeIsoObject;
	import code.tools.sound.src.SoundName;
	import code.untils.IsoStatusConst;
	import code.untils.ItemTypeConst;
	import code.untils.MouseCursorConst;
	import code.untils.SceneConfig;
	
	import com.patience.map.isometric.core.IsoTryResult;
	import com.patience.map.isometric.utils.IsoTypeConst;
	
	import flash.geom.Point;
	
	/**
	 *世界场景diy管理器
	 * @author Yuri
	 *
	 */
	public class DiySceneManager
	{
		private var _isoWorld:YIsoWorld;
		
		private var _diyType:String;
		
		private var _currentDiyIsoObject:YIsoObject;
		
		private var _diyLayer:String;
		/**
		 *是否能放置 是在移动的时候选择的
		 */
		private var _isCanPlace:Boolean;
		/**
		 *检测结果
		 */
		private var _isoTryResult:IsoTryResult;
		
		private var _sceneModel:SceneModel;
		
		private var _controller:SceneController;
		
		/**
		 * diy新增iso来源0：商店面板 1:仓库面板 2:采购车 3:神秘商人 4:招待品尝 5:广告弹窗
		 */
		private var _diyAddIsoSource:int;
		public function DiySceneManager(iWorld:YIsoWorld = null)
		{
			super();
			_isoWorld = iWorld;
//			init();
		}
		
		public function init():void
		{
			diyType =  SceneConfig.SCENE_DIY_NORMAL;
			_diyLayer = SceneConfig.SCENE_DIY_LAYER_OBJECT;
			_isCanPlace = false;
			_isNeedSort = false;
		}
		
		/**
		 *diy 增加物件 
		 * @param d
		 * @param isFromSource 来源 0：商店面板 1：仓库面板 2:采购车
		 */
		public function diyAddIsoObject(d:ItemConfigData,isFromSource:int=0):void{
			if(!_isoWorld) return;
			_isoWorld.status = SceneConfig.SCENE_DIY;
			_diyAddIsoSource = isFromSource;
			var sceneData:SceneItemData = createDiySceneData(d)
			
			//是否在仓库中拥有 todo
			/*if(sceneData.data.storageItem && sceneData.data.storageItem.size>0){
				sceneData.status = 4;
			}*/
			if(d.subType == ItemTypeConst.SUB_FLOOR){
				diyLayer = SceneConfig.SCENE_DIY_LAYER_FLOOR;
			}else{
				diyLayer = SceneConfig.SCENE_DIY_LAYER_OBJECT;
			}
			var iso:YIsoObject = _isoWorld.infoManager.initIsoObject(sceneData);
			if(!iso) return;
			var isoPosition:Point = _isoWorld.getGridPoint3D(_isoWorld.mouseX,_isoWorld.mouseY);
			iso.position3D = _isoWorld.getIsoWorldPoint3DByGridPosition(isoPosition);
			_isoWorld.addToWorld(iso);
			selectDiyCurrentIso(iso);
		}
		
		/**
		 *创建场景diy对象数据 
		 * @param data
		 * @return 
		 * 
		 */
		private function createDiySceneData(data:ItemConfigData):SceneItemData{
			var sceneData:SceneItemData = new SceneItemData();
			sceneData.data = data;
			return sceneData;
		}
		
		/**
		 *选中当前需要diy对象
		 * @param iso
		 *
		 */
		public function selectDiyCurrentIso(iso:YIsoObject):void
		{
			if (!iso)
				return;
			if (!iso.isUnlock) return;
			if(!iso.isCanDiy) return;
			switch (diyType)
			{
				case SceneConfig.SCENE_DIY_NORMAL: 
					currentDiyIsoObject = iso;
					currentDiyIsoObject.showGrid();
					checkDiyPlace();
					currentDiyIsoObject.isMoving = true;
					if (currentDiyIsoObject as WallMuralIsoObject)
					{
						(currentDiyIsoObject as WallMuralIsoObject).originalWallList = (currentDiyIsoObject as WallMuralIsoObject).attachedWallList;
						(currentDiyIsoObject as WallMuralIsoObject).attachedWallList = [];
					}
					break;
				case SceneConfig.SCENE_DIY_ROTATION: 
					//转向
					if (iso as WallMuralIsoObject)
						return;
					currentDiyIsoObject = iso;
					currentDiyIsoObject.direction = iso.direction + 1;
					checkDiyPlace();
					if (_isCanPlace)
					{
						if (currentDiyIsoObject as WallIsoObject)
						{
							if(!recoverWallMural((currentDiyIsoObject as WallIsoObject).attachedMuralList)) {
								cancelCurrentDiy();
								return;
							}
						}
						
						if (_sceneModel.diyMapItem(currentDiyIsoObject, 3))
						{
							if (currentDiyIsoObject is ProductTreeIsoObject)
								MySoundManager.playSound(SoundName.PLANT_TREE);
							else
								MySoundManager.playSound(SoundName.ADD_BUILD_DECORATION_SHELF);
							diySort(currentDiyIsoObject);
							currentDiyIsoObject = null;
						}
					}
					else
					{
						_diyType = SceneConfig.SCENE_DIY_NORMAL;
						selectDiyCurrentIso(currentDiyIsoObject);
						MouseManager.getInstance().followCursorStyle = MouseCursorConst.DIYTYPE_CURSORTYPE_DIC[_diyType];
						return;
					}
					break;
				case SceneConfig.SCENE_DIY_SELL: 
					if(checkIfCanSell(iso))
						sellConfirm(iso);
					break;
				case SceneConfig.SCENE_DIY_RECYCLE: //回收
					//是否需要弹框
					if(checkIsNeedRecyclePop(iso)) return;
					recycleFonfirm(iso);
					break;
			}
		}
		
		/**
		 *检测是否需要回收弹框 
		 * @param iso
		 * 
		 */
		public function checkIsNeedRecyclePop(iso:YIsoObject):Boolean{
			/*if(iso.data.upgradeData && iso.data.upgradeData.harvest_times > 0){
				_isoWorld.sceneAlertManger.showRecoverItemAlert(recycleFonfirm, iso);
				return true;
			}*/
			return false;
		}
		
		/**
		 *确认回收 
		 * @param iso
		 * 
		 */
		public function recycleFonfirm(iso:YIsoObject):void{
			if(!checkIfCanRecyle([iso])) return;
			if (iso as WallIsoObject) //首先判断是出售墙的时候的情况
			{
				if(!recoverWallMural((iso as WallIsoObject).attachedMuralList)) return;
			}
			if (_sceneModel.diyMapItem(iso, 5))
			{
				if (iso as WallIsoObject) //首先判断是出售墙的时候的情况
				{
					if(!recoverWallMural((iso as WallIsoObject).attachedMuralList)) return;
				}
				
				if (iso as WallIsoObject)
				{
					recoverWallMural((iso as WallIsoObject).attachedMuralList);
				}
				_isoWorld.removeFromWorld(iso);
			}
		}
		
		
		/**
		 *检测是否可以被回收 
		 * @param iso
		 * @return 
		 * 
		 */
		private function checkIfCanRecyle(arr:Array):Boolean{
			var count:int = arr.length;
			var iso:YIsoObject;
			for (var i:int; i < count; i++){ 
				iso = arr[i] as YIsoObject;
			}
				return true;
		}
		
		
		/**
		 *检测是否能被立即出售 （能否出售或者需要二次确定） 
		 * @return 
		 * 
		 */
		private function checkIfCanSell(iso:YIsoObject):Boolean{
			//是否存在正确的数值
			if(!iso || !iso.data || !iso.data.data) return false;
			//是否是枯萎的果树
			/*if((iso.data.data.iMarketSubType == ItemTypeConst.SUB_TREE || iso.data.data.iMarketSubType == ItemTypeConst.SUB_PROCUREMENT_GOODS) && (iso as ProductIsoObject).productStatus == ProductStatusConst.PRODUCT_WITHERED_STATUS){
				controller.dispatch(new Command(CommandNameConst.COMMAND_WARN_MSG_ALERT,"WARN_3"));
				return false;
			}*/
			/*   卖任何Cash买到的物品时
			2. 卖普通的物品卖价超过5000金币的时候 ，需弹窗提示确认 */
		/*	if(iso.data.data.sellType == MoneyTypeConst.MONEY_TYPE_CASH || iso.data.data.buyCost >= GameConst.SELL_ITEM_COIN_MAX){
				_isoWorld.sceneAlertManger.showSellItemAlert(iso.data.data,sellConfirm,iso);
				return false;
			}*/
			return true;
		}
		/**
		 *确认出售 （//或者二次弹框确认出售）
		 *
		 */
		public function sellConfirm(_isoObj:YIsoObject):void
		{
			if (_isoObj as WallIsoObject) //首先判断是出售墙的时候的情况
			{
				//先回收
				if(!recoverWallMural((_isoObj as WallIsoObject).attachedMuralList)) return;
			}
			if (_sceneModel.diyMapItem(_isoObj, 4))
			{
				_isoWorld.removeFromWorld(_isoObj);
			}
		}
		
		/**
		 *检测鼠标移动时的diy情况 有选择对象情况下
		 *
		 */
		public function checkDiyStatusByMouseMove(mouseX:Number, mouseY:Number):void
		{
			var isoPosition:Point = _isoWorld.getGridPoint3D(mouseX, mouseY);
			if (currentDiyIsoObject && currentDiyIsoObject.gridX != isoPosition.x || currentDiyIsoObject.gridZ != isoPosition.y)
			{
				currentDiyIsoObject.position3D = _isoWorld.getIsoWorldPoint3DByGridPosition(isoPosition);
				//检测是否可以放置
				checkDiyPlace();
				_isNeedSort = true;
			}
		}
		
		/**
		 *是否需要排序 
		 */
		private var _isNeedSort:Boolean;
		
		/**
		 * 检测鼠标移动停止时的diy情况 有选择对象情况下
		 *
		 */
		public function checkDiyStatusByMouseMoveStop(mouseX:Number, mouseY:Number):void
		{
			if (currentDiyIsoObject && _isNeedSort){
				_isoWorld.sortIsoObjectByAreaDistance(currentDiyIsoObject,5);
				diySort(currentDiyIsoObject);
			}
			_isNeedSort = false;
				
		}
		
		/**
		 *diy排序 
		 * @param iso
		 * 
		 */
		private function diySort(currentDiyIsoObject:YIsoObject):void{
			if(!currentDiyIsoObject) return;
			if(currentDiyIsoObject.classify == IsoTypeConst.ISO_OBJECT_TYPE){
				_isoWorld.sort();
			}else{
				_isoWorld.sortIsoObjectByAreaDistance(currentDiyIsoObject,5);
			}
		}
		
		/**
		 *检测鼠标点击时的diy情况 有选择对象情况下
		 *
		 */
		public function checkDiyStatusByMouseClick(mouseX:Number, mouseY:Number):void
		{
			//检测是否可以放置
			if (_isCanPlace)
			{
				var data:ItemConfigData = currentDiyIsoObject.data.data;
				var isHadScene:Boolean = currentDiyIsoObject.id != null;
				var isSucceed:Boolean = true;
				
				//是否存在在仓库
				var isExistStorage:Boolean ;
				
				
				currentDiyIsoObject.showGrid(false);
				currentDiyIsoObject.status = IsoStatusConst.ISO_STATUS_NORMAL;
				currentDiyIsoObject.isMoving = false;
				//移动  	//一些特殊情况 比如是否会替换原有的地板或者会影响墙上装饰物
				if (currentDiyIsoObject as WallMuralIsoObject)
				{ //墙上装饰物情况下
					(currentDiyIsoObject as WallMuralIsoObject).attachedWallList = _isoTryResult.crossIsoList;
				}
				else if (currentDiyIsoObject as WallIsoObject)
				{
					if(!recoverWallMural((currentDiyIsoObject as WallIsoObject).attachedMuralList)) { //回收不完全成功
						isSucceed = false;
					}
				}
				else if (currentDiyIsoObject as FloorIsoObject)
				{ //地板的话要清空下面的地板层
					if (_isoTryResult && _isoTryResult.crossIsoList && _isoTryResult.crossIsoList.length > 0)
					{
						var count:int = _isoTryResult.crossIsoList.length;
						for (var i:int = 0; i < count; i++)
						{
							var tempF:FloorIsoObject = _isoTryResult.crossIsoList[i] as FloorIsoObject;
							if (tempF)
							{
								if (_sceneModel.diyMapItem(tempF, 5))
								{
									_isoWorld.removeFromWorld(tempF);
								}else{
									isSucceed = false;
									break;
								}
							}
						}
					}
				}
				if(isSucceed) //前面判断都成功的前提下才能做移动操作
				isSucceed = _sceneModel.diyMapItem(currentDiyIsoObject, 2);
				if (isSucceed)
				{
					//是否存在在仓库中
				/*	isExistStorage = data.storageItem && data.storageItem.size > 0*/
					if (currentDiyIsoObject is ProductTreeIsoObject)
						MySoundManager.playSound(SoundName.PLANT_TREE);
					else
						MySoundManager.playSound(SoundName.ADD_BUILD_DECORATION_SHELF);
					currentDiyIsoObject = null; //放置成功
					_isCanPlace = false;
				}
				else
				{
					cancelCurrentDiy();
					return;
				}
				if (!isHadScene)//不是场景中原本存在的物件
				{ 
					//检测当前是否还是在diy状态
					if(_isoWorld.status != SceneConfig.SCENE_DIY) return;
					/*if(_diyAddIsoSource==0 && data.iUnlock == 0){
						diyAddIsoObject(data,_diyAddIsoSource);
					}else if(_diyAddIsoSource==1 && isExistStorage){
						diyAddIsoObject(data,_diyAddIsoSource);
					}*/
				}
			}
		}
		
		/**
		 *取消当前操作
		 *
		 */
		public function cancelCurrentDiy():void
		{
			if (!currentDiyIsoObject)
				return;
			if (!currentDiyIsoObject.id)
			{
				_isoWorld.removeFromWorld(currentDiyIsoObject);
				currentDiyIsoObject = null;
				return;
			}
			if (currentDiyIsoObject)
			{
				switch (diyType)
				{
					case SceneConfig.SCENE_DIY_SELL: 
						currentDiyIsoObject = null;
						break;
					default: 
						currentDiyIsoObject.showGrid(false);
						currentDiyIsoObject.position3D = currentDiyIsoObject.data.position3D;
						currentDiyIsoObject.direction = currentDiyIsoObject.data.direction;
						currentDiyIsoObject.status = IsoStatusConst.ISO_STATUS_NORMAL;
						currentDiyIsoObject.isMoving = false;
						if (currentDiyIsoObject as WallMuralIsoObject)
						{ //墙上装饰特使处理
							(currentDiyIsoObject as WallMuralIsoObject).attachedWallList = (currentDiyIsoObject as WallMuralIsoObject).originalWallList;
						}
						diySort(currentDiyIsoObject);
						break;
				}
			}
			currentDiyIsoObject = null;
			_isCanPlace = false;
			_isNeedSort = false
		}
		
		/**
		 *退出
		 *
		 */
		public function exit():void
		{
			_diyType = null;
			diyLayer = SceneConfig.SCENE_DIY_LAYER_OBJECT;
			MouseManager.getInstance().clearFollowCursor();
			cancelCurrentDiy();
			_isNeedSort = false;
		}
		
		/**
		 *检测diy是否可以放置
		 *
		 */
		private function checkDiyPlace():void
		{
			
			if (checkIfEffectArea())
			{
				_isoTryResult = _isoWorld.checkIsoObjectPlace(currentDiyIsoObject);
				if (currentDiyIsoObject as WallMuralIsoObject)
				{ //特殊处理墙上装饰物
					if (_isoTryResult.isSucess)
					{
						checkMural();
						_isCanPlace = _isoTryResult.isSucess;
						if (diyType == SceneConfig.SCENE_DIY_NORMAL)
							currentDiyIsoObject.status = _isCanPlace ? IsoStatusConst.ISO_STATUS_ABLE_PLACE : IsoStatusConst.ISO_STATUS_DISABLE_PLACE;
						if(_isoTryResult.isSucess){
							var cList:Array = _isoTryResult.crossIsoList;
							_isoTryResult = _isoWorld.checkIsoObjectPlace(currentDiyIsoObject);
							_isoTryResult.isSucess?_isoTryResult.crossIsoList=cList:1;
						}
					}
				}
				_isCanPlace = _isoTryResult.isSucess;
			}
			else
			{
				_isCanPlace = false;
			}
			
			if (diyType == SceneConfig.SCENE_DIY_NORMAL)
				currentDiyIsoObject.status = _isCanPlace ? IsoStatusConst.ISO_STATUS_ABLE_PLACE : IsoStatusConst.ISO_STATUS_DISABLE_PLACE;
		}
		
		/**
		 *检测是否在有效的区域内
		 *
		 */
		private function checkIfEffectArea():Boolean
		{
			var checkBoolean:Boolean = _isoWorld.mapInfo.areaInfo.checkAreaIsUnLocked(currentDiyIsoObject.gridX, currentDiyIsoObject.gridZ);
			if (!checkBoolean)
				return false;
			if (currentDiyIsoObject.floorXCount > 1 || currentDiyIsoObject.floorZCount > 1)
			{
				checkBoolean = _isoWorld.mapInfo.areaInfo.checkAreaIsUnLocked(currentDiyIsoObject.gridX + currentDiyIsoObject.floorXCount - 1, currentDiyIsoObject.gridZ + currentDiyIsoObject.floorZCount - 1);
				if (!checkBoolean)
					return false;
				checkBoolean = _isoWorld.mapInfo.areaInfo.checkAreaIsUnLocked(currentDiyIsoObject.gridX + currentDiyIsoObject.floorXCount - 1, currentDiyIsoObject.gridZ);
				if (!checkBoolean)
					return false;
				checkBoolean = _isoWorld.mapInfo.areaInfo.checkAreaIsUnLocked(currentDiyIsoObject.gridX , currentDiyIsoObject.gridZ + currentDiyIsoObject.floorZCount - 1);
			}
			return checkBoolean;
		}
		
		/**
		 *检测墙上装饰物是否有墙可以依附
		 *
		 */
		private function checkMural():void
		{
			var leftPlace:Boolean = false;
			var rightPlace:Boolean = false;
			if(!currentDiyIsoObject) return;
			
			if(currentDiyIsoObject.direction == 1){//先判断右上角
				rightPlace = checkMuralPlace();
				if (rightPlace)
				{ 
					currentDiyIsoObject.showGrid();
				}else{
					leftPlace = checkMuralPlace(1); //再判断左上角
					if (leftPlace)
					{
						currentDiyIsoObject.direction = 2;
						currentDiyIsoObject.showGrid();
					}
				}
			}else{//先判断左上角
				leftPlace = checkMuralPlace(1);
				if(leftPlace){
					currentDiyIsoObject.showGrid();
				}else{
					rightPlace = checkMuralPlace();
					if (rightPlace)
					{ 
						currentDiyIsoObject.direction = 1;
						currentDiyIsoObject.showGrid();
					}
				}
			}
			_isoTryResult.isSucess = rightPlace || leftPlace;
		}
		
		/**
		 *
		 * @param direction 0：右上角 1：左上角
		 *
		 */
		private function checkMuralPlace(direction:int = 0):Boolean
		{
			var count:int;
			var list:Array = [];
			var i:int = 0;
			var muralLength:int;
			var wallLength:int;
			
			if (direction == 0)
			{
				muralLength = currentDiyIsoObject.direction==1?currentDiyIsoObject.floorXCount:currentDiyIsoObject.floorZCount;
				list = _isoWorld.getObjectListByRange(currentDiyIsoObject.gridX, currentDiyIsoObject.gridZ - 1, currentDiyIsoObject.gridX+muralLength/*currentDiyIsoObject.maxIsoPosition.x*/, currentDiyIsoObject.gridZ - 1, currentDiyIsoObject.classify);
			}
			else
			{
				muralLength = currentDiyIsoObject.direction==1?currentDiyIsoObject.floorXCount:currentDiyIsoObject.floorZCount;
				list = _isoWorld.getObjectListByRange(currentDiyIsoObject.gridX - 1, currentDiyIsoObject.gridZ, currentDiyIsoObject.gridX - 1, currentDiyIsoObject.gridZ+muralLength/*currentDiyIsoObject.maxIsoPosition.y*/, currentDiyIsoObject.classify);
			}
			
			count = list.length;
			
			for (i = 0; i < count; i++)
			{
				var isoTemp:YIsoObject = list[i] as YIsoObject;
				if (isoTemp && isoTemp is WallIsoObject && (isoTemp as WallIsoObject).isCanAttach)
				{ //是墙 并且是可以依附的墙
					wallLength += direction == 0 ? isoTemp.floorXCount : isoTemp.floorZCount;
				}
				/*else
				{
					return false;
				}*/
			}
			if (wallLength >= muralLength)
			{
				_isoTryResult.crossIsoList = list;
				return true;
			}
			return false;
		}
		
		/**
		 * 回收墙上装饰
		 * @param arr
		 *
		 */
		private function recoverWallMural(arr:Array):Boolean
		{
			 //首先做一轮过滤是否可以回收
			if(!checkIfCanRecyle(arr)) return false;
			var cloneArr:Array = arr.concat();
			var count:int = cloneArr.length;
			
			for (var i:int; i < count; i++)
			{
				var iso:WallMuralIsoObject = cloneArr[i] as WallMuralIsoObject;
				if (iso && _sceneModel.diyMapItem(iso, 5))
				{
					_isoWorld.removeFromWorld(iso);
				}
			}
			return true;
		}
		
		
		/**
		 *世界
		 */
		public function set isoWorld(value:YIsoWorld):void
		{
			_isoWorld = value;
		}
		
		/**
		 *当前diy对象
		 */
		public function get currentDiyIsoObject():YIsoObject
		{
			return _currentDiyIsoObject;
		}
		
		/**
		 * @private
		 */
		public function set currentDiyIsoObject(value:YIsoObject):void
		{
			_currentDiyIsoObject = value;
		}
		
		/**
		 *diy类型
		 */
		public function get diyType():String
		{
			return _diyType;
		}
		
		/**
		 * @private
		 */
		public function set diyType(value:String):void
		{
			if (_diyType == value)
				return;
			cancelCurrentDiy();
			_diyType = value;
			MouseManager.getInstance().followCursorStyle = MouseCursorConst.DIYTYPE_CURSORTYPE_DIC[_diyType];
		}
		
		/**
		 *diy层级
		 */
		public function get diyLayer():String
		{
			return _diyLayer;
		}
		
		/**
		 * @private
		 */
		public function set diyLayer(value:String):void
		{
			if (diyLayer == value)
				return;
			/*if(value == SceneConfig.SCENE_DIY_LAYER_FLOOR && diyLayer == value ){
			   value = SceneConfig.SCENE_DIY_LAYER_OBJECT;
			 }*/
			_diyLayer = value;
			
			if (!_isoWorld)
				return;
			cancelCurrentDiy();
			switch (value)
			{
				case SceneConfig.SCENE_DIY_LAYER_OBJECT: 
					_isoWorld.worldObjectLayerMouseEnable = true;
					_isoWorld.worldFloorLayerMouseEnable = false;
					_isoWorld.worldObjectLayerAlpha = 1;
					_isoWorld.isNeedFloorSort = false;
					_isoWorld.isNeedObjectSort = true;
					break;
				case SceneConfig.SCENE_DIY_LAYER_FLOOR: 
					_isoWorld.worldObjectLayerMouseEnable = false;
					_isoWorld.worldFloorLayerMouseEnable = true;
					_isoWorld.worldObjectLayerAlpha = .5;
					_isoWorld.isNeedFloorSort = true;
					_isoWorld.isNeedObjectSort = false;
					break;
			}
		}
		
		public function get controller():SceneController
		{
			return _controller;
		}
		
		public function set controller(value:SceneController):void
		{
			_controller = value;
			if (value)
				_sceneModel = _controller.sceneModel;
		}
		
		public function clear():void
		{
			cancelCurrentDiy();
			init();
		}
	}
}